<?php

namespace app\api\controller\xmwechat;

use app\common\controller\Frontend;
use app\common\library\xmwechat\miniprogram\MpService;
use app\common\model\User;
use think\db\exception\PDOException;
use think\exception\ValidateException;
use think\Request;

/**
 * 小程序登录
 */
class Miniprogram extends Frontend
{
    protected array $noNeedLogin = ['phoneLogin','autologin','getOpenidAndUnionid', 'getPhoneNumber', 'checkText', 'checkMedia', 'messageServe'];

    public function initialize(): void
    {
        parent::initialize();
    }

    /**
     * 微信小程序获取Openid和Unionid示例（若绑定微信开放平台，获取不到Unionid，只能获取Openid）
     * @param Request $request
     * @return void
     * @author jsjxsz <QQ:1365962177>
     */
    public function getOpenidAndUnionid(Request $request): void
    {
        if ($request->isPost()) {
            // code 前端获取，传递给接口
            $params = $request->only(['code']);
            $result = MpService::getInstance()->getOpenidAndUnionid($params);
            if (!empty($result)) {
                // 这里获取到Openid、Unionid，写你自己的逻辑

                $this->success('success', $result);
            } else {
                $this->error('error');
            }

        }
    }

    /**
     * 微信小程序获取手机号示例
     * @param Request $request
     * @return void
     * @author jsjxsz <QQ:1365962177>
     */
    public function getPhoneNumber(Request $request): void
    {
        if ($request->isPost()) {
            // code 前端获取，传递给接口
            $params = $request->only(['code']);
            $result = MpService::getInstance()->getPhoneNumber($params);
            if (!empty($result)) {
                // 这里获取到手机号，写你自己的逻辑
                $this->success('success', $result);
            } else {
                $this->error('error');
            }
        }
    }

    /**
     *  sendSms 手机号登录示例
     * @param Request $request
     * @return void
     */
    #[
        Apidoc\Title("手机号登录示例"),
        Apidoc\Tag("手机号授权过"),
        Apidoc\Method("POST"),
        Apidoc\Url("/api/xmwechat.Miniprogram/phoneLogin"),
        Apidoc\Param(name:"login_code",type: "string",require: true,desc: "wx.login的code",mock:""),
        Apidoc\Param(name:"code",type: "string",require: true,desc: "获取手机号的code",mock:""),
        Apidoc\Returned("id",type: "int",desc: "Id"),
    ]
    public function phoneLogin(Request $request): void
    {
        if ($request->isPost()) {
            // code 前端获取，传递给接口
            $params = $request->only(['code', 'login_code']);
            $login_data = ['code' => $params['login_code']];
            $openidinfo = MpService::getInstance()->getOpenidAndUnionid($login_data);
            if (empty($openidinfo)) {
                $this->error('获取openid失败');
            }
            $result = MpService::getInstance()->getPhoneNumber($params);
//            $openidinfo=["openid"=> "oza8S7TKJwn-bxgGHz-LUSfUbbik",
//                "unionid"=> ""
//            ];
//            $result=json_decode('{
//                "errcode": 0,
//			"errmsg": "ok",
//			"phone_info": {
//                "phoneNumber": "14787826552",
//				"purePhoneNumber": "14787826552",
//				"countryCode": "86",
//				"watermark": {
//                    "timestamp": 1715003331,
//					"appid": "wx2b1b3222bf4cab2b"
//				}
//			}
//		}',true);
            if (!empty($result)&&$result['errcode']==0) {
                $mobile = $result['phone_info']['purePhoneNumber'];
                // 这里获取到手机号，写你自己的逻辑
                $urow = (new User())->where('mobile', $mobile)->find();

                if ($urow) {
                    $this->auth->direct($urow['id']);
                } else {
                    $extent_data = [
                        'mini_openid' => $openidinfo['openid'],
                        'weixin_unionid' => $openidinfo['unionid'],
                        'nickname' =>'手机用户'.substr($mobile,7,11),
                    ];
                    $regsult=$this->auth->register('bzg'.$mobile, '123456', $mobile, '', 1, $extent_data);

                    if ($regsult) {
                        $this->auth->direct($this->auth->id);   // 直接登录
                    } else {
                        $this->error($this->auth->getError());
                    }
                }
                $this->success(__('Login succeeded!'), [
                    'userInfo' => $this->auth->getUserInfo()
                ]);
            } else {
                $this->error('error');
            }
        }
    }

    /**
     * 自动登录示例
     * 手机号授权过后才能有账号
     */
    #[
        Apidoc\Title(" 自动登录示例"),
        Apidoc\Tag("手机号授权过后才能有账号"),
        Apidoc\Method("POST"),
        Apidoc\Url("/api/xmwechat.Miniprogram/autologin"),
        Apidoc\Param(name:"login_code",type: "string",require: true,desc: "wx.login的code",mock:""),
        Apidoc\Returned("id",type: "int",desc: "Id"),
    ]
    public function autologin(Request $request): void
    {
        if ($request->isPost()) {
            $params = $request->only(['login_code']);
            $params['code'] = $params['login_code'];
            $result = MpService::getInstance()->getOpenidAndUnionid($params);
            if (!empty($result)) {
                // 这里获取到Openid、Unionid，写你自己的逻辑
                $urow=(new User())->where('mini_openid', $result['openid'])->find();
                if(empty($urow)){
                    $this->error($result['openid'],$result);
                }
                if(isset($result['unionid'])&&!empty($result['unionid'])){
                    $urow->save([
                        'weixin_unionid'=>$result['unionid']
                    ]);
                }

                $this->auth->direct($urow['id']);
                $this->success(__('Login succeeded!'), [
                    'userInfo' => $this->auth->getUserInfo(),
                    '$result'=>$result
                ]);
            } else {
                $this->error('error');
            }
        }
    }

    /**
     * 微信小程序文本内容安全识别示例
     * 单个appid调用上限为2000次/分钟，1,000,000次/天
     * openid 用户openid，需在近两小时访问过小程序
     * scene 场景枚举值（1 资料；2 评论；3 论坛；4 社交日志）
     * @param Request $request
     * @return void
     * @author jsjxsz <QQ:1365962177>
     */
    public function checkText(Request $request): void
    {
        if ($request->isPost()) {
            // openid 用户需在近两小时访问过小程序
            $params = $request->only(['openid', 'scene', 'content']);
            $result = MpService::getInstance()->checkText($params);
            if ($result !== false) {
                $this->success('文本内容-检测通过');
            } else {
                $this->error('文本内容-检测未通过');
            }
        }
    }

    /**
     * 微信小程序音视频内容安全识别示例
     * openid 用户openid，需在近两小时访问过小程序
     * media_type 1:音频; 2:图片
     * scene 场景枚举值（1 资料；2 评论；3 论坛；4 社交日志）
     * media_url 要检测的图片或音频的url，支持图片格式包括jpg, jepg, png, bmp, gif（取首帧），支持的音频格式包括mp3, aac, ac3, wma, flac, vorbis, opus, wav
     * @param Request $request
     * @return void
     * @throws \Exception
     * @author jsjxsz <QQ:1365962177>
     */
    public function checkMedia(Request $request): void
    {
        if ($request->isPost()) {
            $params = $request->only(['openid', 'media_type', 'scene', 'media_url']);
            $result = MpService::getInstance()->checkMedia($params);
            if ($result !== false) {

                // 这里写你自己的逻辑

                $this->success('音频/图片内容-检测请求成功，检测结果微信会异步推送。接收微信异步推送的方法(messageServe): app/api/controller/xmwechat/Miniprogram.php');
            } else {
                $this->error('音频/图片内容-检测请求未成功');
            }
        }
    }

    /**
     * 微信小程序 音视频内容安全识别结果推送示例
     * 需要在后台【微信管理】【小程序】【配置管理】中配置消息推送的相关参数
     * @param Request $request
     * @author jsjxsz <QQ:1365962177>
     */
    public function messageServe(Request $request)
    {
        $jsonData = file_get_contents("php://input");
        $params = $request->param(['signature', 'timestamp', 'nonce', 'echostr']);
        try {
            if (isset($params['echostr']) && !empty($params['echostr'])) {
                $res = MpService::getInstance()->checkSignature($params);
                if ($res !== false) {
                    echo $params['echostr'];
                } else {
                    echo '验证失败';
                }
                exit();
            }
            $data = json_decode($jsonData, true);
            if (!empty($data)) {
                if (isset($params['errmsg']) && isset($params['errcode']) && isset($params['result'])) {
                    //result 为综合结果，包含的属性有
                    //suggest 建议，有risky、pass、review三种值
                    //label 命中标签枚举值，100 正常；20001 时政；20002 色情；20006 违法犯罪；21000 其他
                    $trace_id = $params['trace_id'];
                    if ($params['result']['label'] !== 100) {
                        /**
                         * 此处根据命中标签枚举值和trace_id处理自己的相关逻辑
                         */

                    }
                }
            }
        } catch (ValidateException|PDOException $e) {
            $this->error($e->getMessage());
        }
    }
}
